数据类型转化表
首先上数据类型转化表,便于遇到问题直接查看
值 | 字符串 | 数字 | 布尔值 | 对象 |
---|---|---|---|---|
undefined null |
"undefined" "null" |
NaN | false false |
throws TypeError throws TypeError |
true false |
"true" "false" |
1 0 |
new Boolean(true) new Boolean(false) |
|
""(空字符串) "1.2"(非空,数字) "one"(非空,非数字) |
0 1.2 NaN |
false true true |
new String("") new String("1.2") new String("one") |
|
0 -0 NaN Infinity -Infinity 1(非零) |
"0" "0" "NaN" "Infinity" "-Infinity" "1" |
new Number(0) new Number(-0) new Number(NaN) new Number(Infinity) new Number(-Infinity) new Number(1) |
||
{}(任意对象) [] [9] ["a"] |
{}.toString() -> {}.valueOf() "" "9" 使用join() |
{}.valueOf() -> {}.toString() 0 9 NaN NaN |
true true true true |
显式转换
显示转换最简单的是使用Boolean()、Number()、String()或Object()构造函数
Number("3"); // 3
String(false); // "false"
Boolean([]); // true
Object(3); // new Number(3)
ps:值得注意的是,试图把undefined或null转换为对象,会抛出一个类型错误,而Object()显示转换不会,而是返回一个新创建的空对象
显示转换还有toString()
、toFixed()
、toExponential()
、toPrecision()
、parseInt()
、parseFloat()
方法,不细说
隐式转换
隐式转换分为三种:
- 将值转换为原始值,ToPrimitive(input, PreferredType)
- 将值转化为数字,ToNumber()
- 将值转化为字符串,ToString()
原始类型数据转化相对比较简单,下面值看对象到原始类型的转换方式
对象的toString()和valueOf()方法
-
所有对象继承了两个转换方法:
toString()
- 一般对象转化成[object object]
{x: 1, y: 2}.toString(); // "[object object]"
- 数组转化成元素间加逗号
[1, 2, 3].toString(); // "1,2,3"
- 函数转化成定义
(function(x){}).toString(); // "function(x) {}"
- 正则转化为直接量字符串
/\d+/g.toString(); // "/\d+/g"
- 日期转化为日期字符串
new Date(2000, 1, 1).toString();
// "Tue Feb 01 2000 00:00:00 GMT+0800 (中国标准时间)"
- 一般对象转化成[object object]
-
valueOf()
方法- 大多数对象无法真正表示为一个原始值,
valueOf()
简单返回对象本身 - 日期对象是一个特例,返回毫秒数
new Date(2010, 0, 1).valueOf(); // 12623328000
- 大多数对象无法真正表示为一个原始值,
对象到字符串的转换
- 如果对象具有toString()方法,则调用这个方法,如果它返回一个原始值,将这个值转化为字符串,并返回这个字符串结果
- 如果对象没有toString()方法,或者个这个方法不返回一个原始值,那么就会调用valueOf()方法。如果存在这个方法,则调用它,如果返回值是一个原始值,将这个值转化为只服从,并返回这个字符串结果
- 否则,就会抛出一个类型错误异常
对象到数字的转换
- 如果对象具有valueOf()方法,后者返回个亿原始值,则将这个原始值转化为数字,并返回这个数字
- 否则,如果对象有toString()方法,后者返回一个原始值,并转化成数字返回
- 否则,抛出一个类型错误异常
举个栗子: ({} + {}) = ?
两个对象的值进行+运算符,要先进行隐式转换成原始类型才能计算
1. ToPrimitive转换,因为没有指定PreferredType类型,默认为Number
2. 执行`valueOf()`方法,`{}.valueOf()`返回的还是{}对象
3. 继续执行`toString()`方法,`({}).toString()`返回`[Object Object]`,是原始值
所以最后结果:[Object Object][Object Object]
ps:在Firefox中返回结果为NaN
,因为第一个{}被当作一个代码块,没有解析转换,变成了+{}
,也就是+[Object Object]
,最终变成NaN
==元算符隐式转换
==运算符应用和考察点很多,直接上ES5规范文档
比较运算 x==y, 其中 x 和 y 是值,返回 true 或者 false。这样的比较按如下方式进行:
1、若 Type(x) 与 Type(y) 相同, 则
1* 若 Type(x) 为 Undefined, 返回 true。
2* 若 Type(x) 为 Null, 返回 true。
3* 若 Type(x) 为 Number, 则
(1)、若 x 为 NaN, 返回 false。
(2)、若 y 为 NaN, 返回 false。
(3)、若 x 与 y 为相等数值, 返回 true。
(4)、若 x 为 +0 且 y 为 −0, 返回 true。
(5)、若 x 为 −0 且 y 为 +0, 返回 true。
(6)、返回 false。
4* 若 Type(x) 为 String, 则当 x 和 y 为完全相同的字符序列(长度相等且相同字符在相同位置)时返回 true。 否则, 返回 false。
5* 若 Type(x) 为 Boolean, 当 x 和 y 为同为 true 或者同为 false 时返回 true。 否则, 返回 false。
6* 当 x 和 y 为引用同一对象时返回 true。否则,返回 false。
2、若 x 为 null 且 y 为 undefined, 返回 true。
3、若 x 为 undefined 且 y 为 null, 返回 true。
4、若 Type(x) 为 Number 且 Type(y) 为 String,返回比较 x == ToNumber(y) 的结果。
5、若 Type(x) 为 String 且 Type(y) 为 Number,返回比较 ToNumber(x) == y 的结果。
6、若 Type(x) 为 Boolean, 返回比较 ToNumber(x) == y 的结果。
7、若 Type(y) 为 Boolean, 返回比较 x == ToNumber(y) 的结果。
8、若 Type(x) 为 String 或 Number,且 Type(y) 为 Object,返回比较 x == ToPrimitive(y) 的结果。
9、若 Type(x) 为 Object 且 Type(y) 为 String 或 Number, 返回比较 ToPrimitive(x) == y 的结果。
10、返回 false。
总结起来有如下几点值得注意
NaN !== NaN
- x,y 为null、undefined两者中一个 // 返回true
- x、y为Number和String类型时,则转换为Number类型比较
- 有Boolean类型时,Boolean转化为Number类型比较
- 一个Object类型,一个String或Number类型,将Object类型进行原始转换后,按上面流程进行原始值比较
举一个栗子:
var a = {
valueOf: function () {
return1;
},
toString: function () {
return'123'
}
}
console.log(rue == a) // true;
1. 首先,x与y类型不同,x为boolean类型,则进行ToNumber转换为1,为number类型
2. x为number,y为object类型,对y进行原始转换,ToPrimitive(a, ?),没有指定转换类型,默认number类型
3. ToPrimitive(a, Number)首先调用valueOf方法,返回1,得到原始类型1。
4. 1 == 1, 返回true
同理适用于>
、<
、!=
、+
运算符的隐式转换(但要除去日期对象)
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。